package org.hisp.dhis.wsclient.j2me.javarosa;

import java.util.Enumeration;
import java.util.Vector;

import javax.microedition.lcdui.Command;
import javax.microedition.lcdui.CommandListener;
import javax.microedition.lcdui.Displayable;

import org.hisp.dhis.wsclient.dao.DataValueDAO;
import org.hisp.dhis.wsclient.dao.DatasetDAO;
import org.hisp.dhis.wsclient.dao.mockup.MockupDataValueDAO;
import org.hisp.dhis.wsclient.dao.mockup.MockupDatasetDAO;
import org.hisp.dhis.wsclient.model.DataElement;
import org.hisp.dhis.wsclient.model.DataValue;
import org.hisp.dhis.wsclient.model.Dataset;
import org.hisp.dhis.wsclient.model.OrganisationUnit;
import org.hisp.dhis.wsclient.model.Period;
import org.javarosa.core.Context;
import org.javarosa.core.api.Constants;
import org.javarosa.core.api.IActivity;
import org.javarosa.core.api.IShell;

import de.enough.polish.ui.Choice;
import de.enough.polish.ui.ChoiceGroup;
import de.enough.polish.ui.ChoiceItem;
import de.enough.polish.ui.Form;
import de.enough.polish.ui.Item;
import de.enough.polish.ui.StringItem;
import de.enough.polish.ui.TextField;

public class DataEntryActivity
    implements IActivity, CommandListener
{
    public static final String CMD_CANCEL = "cancel";
    private IShell shell;
    private Keys keys;
    private Context context;

    private Form form;

    private Command cmdCancel;
    private Command cmdFinish;

    private DatasetDAO datasetDAO;
    private DataValueDAO datavalueDAO;

    private OrganisationUnit orgunit;
    private Dataset dataset;
    private Period period;

    private Vector fields;

    public DataEntryActivity( IShell shell, Keys keys )
    {
        setShell( shell );
        this.keys = keys;

        cmdFinish = new Command( "Select period", Command.OK, 0 );
        cmdCancel = new Command( "Cancel", Command.CANCEL, 0 );

        datasetDAO = new MockupDatasetDAO();
        datavalueDAO = new MockupDataValueDAO();
    }

    public void contextChanged( Context globalContext )
    {
        // TODO Auto-generated method stub

    }

    public void destroy()
    {
        // TODO Auto-generated method stub

    }

    public Context getActivityContext()
    {
        // TODO Auto-generated method stub
        return null;
    }

    public void halt()
    {
        // TODO Auto-generated method stub

    }

    public void resume( Context globalContext )
    {
        shell.setDisplay( this, Util.createIView( form ) );
    }

    public void setShell( IShell shell )
    {
        this.shell = shell;
    }

    public void start( Context context )
    {
        this.context = context;

        orgunit = (OrganisationUnit) context.getElement( keys.ORGUNIT );
        dataset = (Dataset) context.getElement( keys.DATASET );
        period = (Period) context.getElement( keys.PERIOD );

        dataset = datasetDAO.getDataset( orgunit, period, dataset );

        fields = new Vector();
        Field field;
        for ( int i = 0; i < dataset.getDataElements().size(); i++ )
        {
            field = new Field();
            field.element = (DataElement) dataset.getDataElements().elementAt( i );

            // Find datavalue for dataelement if there is one
            for ( Enumeration e = dataset.getDataValues().elements(); e.hasMoreElements(); )
            {
                field.value = (DataValue) e.nextElement();
                if ( field.value.getDataElement() == field.element )
                {
                    break;
                }
                else
                {
                    field.value = null;
                }
            }
            fields.addElement( field );
        }

        form = createScreen( orgunit, dataset, period, fields );
        shell.setDisplay( this, Util.createIView( form ) );
    }

    private Form createScreen( OrganisationUnit orgunit, Dataset dataset, Period period, Vector fields )
    {
        //#style .formScreen, .baseScreen
        Form form = new Form( "Dataentry" );

        //#style .baseText
        form.append( new StringItem( "Organisation Unit:", orgunit.getName() ) );
        //#style .baseText
        form.append( new StringItem( "Dataset:", dataset.getName() ) );
        //#style .baseText
        form.append( new StringItem( "Period:", period.getName() ) );

        form.addCommand( cmdFinish );
        form.addCommand( cmdCancel );

        Field field;
        for ( Enumeration e = fields.elements(); e.hasMoreElements(); )
        {
            field = (Field) e.nextElement();
            DataElement element = field.element;
            DataValue value = field.value;
            Item item;
            String v = "";
            if ( element.getType() == "string" )
            {
                if ( value != null )
                    v = value.getValue();
                //#style .textfieldItem, .baseText
                item = new TextField( element.getName(), v, 100, TextField.ANY );
            }
            else if ( element.getType() == "int" )
            {
                if ( value != null )
                    v = value.getValue();
                //#style .decimalTextfieldItem, .textfieldItem, .baseText
                item = new TextField( element.getName(), v, 100, TextField.DECIMAL );
            }
            else if ( element.getType() == "bool" )
            {
                //#style .singleCheckboxItem, .choicegroupItem, .baseText
                ChoiceGroup cg = new ChoiceGroup( "", Choice.EXCLUSIVE );

                //#style .checkbox, .choiceItem, .baseText
                ChoiceItem checkbox = new ChoiceItem( element.getName(), null, Choice.EXCLUSIVE );
                cg.add( checkbox );

                if ( value != null )
                    v = value.getValue();
                boolean checked = (v == "1") ? true : false;
                cg.setSelectedIndex( 0, checked );

                item = cg;
            }
            else
            {
                //#style .stringItem, .baseText
                item = new StringItem( element.getName(), "Element type '" + element.getType() + "' not supported." );
            }

            field.item = item;
            form.append( item );
        }
        form.setCommandListener( this );

        return form;
    }

    public void commandAction( Command cmd, Displayable display )
    {
        if ( cmd == cmdFinish )
        {
            shell.returnFromActivity( this, Constants.ACTIVITY_COMPLETE, null );
        }
    }

    private class Field
    {
        public DataElement element;
        public DataValue value;
        public Item item;
    }
}
